package handler

import (
	"fitness/go-admin/internal/model"
	"fitness/go-admin/internal/service"
	"fitness/go-admin/pkg/errcode"
	"fitness/go-admin/pkg/logger"
	"fitness/go-admin/pkg/response"
	"strconv"

	"github.com/gin-gonic/gin"
)

type UserHandler struct {
	service service.UserService
}

func NewUserHandler(service service.UserService) *UserHandler {
	return &UserHandler{service: service}
}

// List 获取用户列表
// @Summary 获取用户列表
// @Tags 用户管理
// @Produce json
// @Param page query int false "页码" default(1)
// @Param pageSize query int false "每页数量" default(10)
// @Param role query string false "角色筛选(admin/coach/member)"
// @Param status query int false "状态筛选(0:禁用 1:启用)"
// @Param keyword query string false "搜索关键词(用户名/邮箱/手机号)"
// @Success 200 {object} response.PageResponse
// @Router /api/v1/users [get]
func (h *UserHandler) List(c *gin.Context) {
	var req model.UserListReq
	if err := c.ShouldBindQuery(&req); err != nil {
		response.Error(c, errcode.BadRequest, "参数错误: "+err.Error())
		return
	}

	// 设置默认值
	if req.Page == 0 {
		req.Page = 1
	}
	if req.PageSize == 0 {
		req.PageSize = 10
	}

	users, total, err := h.service.GetUserList(&req)
	if err != nil {
		logger.Error("获取用户列表失败", "error", err.Error())
		response.Error(c, errcode.InternalError, err.Error())
		return
	}

	// 记录审计日志
	adminID, _ := c.Get("userId")
	logger.LogAudit(logger.AuditLog{
		UserID:    adminID.(uint),
		Action:    "VIEW_USER_LIST",
		Resource:  "user",
		IP:        c.ClientIP(),
		UserAgent: c.GetHeader("User-Agent"),
		Details:   "查询参数: " + c.Request.URL.RawQuery,
	})

	response.SuccessWithPage(c, users, total, req.Page, req.PageSize, "获取成功")
}

// Get 获取用户详情
// @Summary 获取用户详情
// @Tags 用户管理
// @Produce json
// @Param id path int true "用户ID"
// @Success 200 {object} response.Response{data=model.UserDetailResp}
// @Router /api/v1/users/:id [get]
func (h *UserHandler) Get(c *gin.Context) {
	// 获取用户ID参数
	id, err := strconv.ParseUint(c.Param("id"), 10, 32)
	if err != nil {
		response.Error(c, errcode.BadRequest, "用户ID格式错误")
		return
	}

	// 调用Service层获取详情
	detail, err := h.service.GetUserDetail(uint(id))
	if err != nil {
		logger.Error("获取用户详情失败", "userId", id, "error", err.Error())
		response.Error(c, errcode.UserNotFound, err.Error())
		return
	}

	// 记录审计日志
	adminID, _ := c.Get("userId")
	logger.LogAudit(logger.AuditLog{
		UserID:    adminID.(uint),
		Action:    "VIEW_USER_DETAIL",
		Resource:  "user",
		IP:        c.ClientIP(),
		UserAgent: c.GetHeader("User-Agent"),
		Details:   "查看用户ID: " + strconv.FormatUint(id, 10),
	})

	response.Success(c, detail, "获取成功")
}

// Update 更新用户信息
// @Summary 更新用户信息
// @Tags 用户管理
// @Accept json
// @Produce json
// @Param id path int true "用户ID"
// @Param body body model.UpdateUserReq true "更新信息"
// @Success 200 {object} response.Response
// @Router /api/v1/users/:id [put]
func (h *UserHandler) Update(c *gin.Context) {
	// 获取用户ID参数
	id, err := strconv.ParseUint(c.Param("id"), 10, 32)
	if err != nil {
		response.Error(c, errcode.BadRequest, "用户ID格式错误")
		return
	}

	// 绑定请求参数
	var req model.UpdateUserReq
	if err := c.ShouldBindJSON(&req); err != nil {
		response.Error(c, errcode.BadRequest, "参数错误: "+err.Error())
		return
	}

	// 调用Service层更新
	if err := h.service.UpdateUserInfo(uint(id), &req); err != nil {
		logger.Error("更新用户信息失败", "userId", id, "error", err.Error())

		// 根据错误信息返回不同的错误码
		errMsg := err.Error()
		switch errMsg {
		case "用户不存在":
			response.Error(c, errcode.UserNotFound, errMsg)
		case "邮箱已被其他用户使用":
			response.Error(c, errcode.EmailExists, errMsg)
		case "手机号已被其他用户使用":
			response.Error(c, errcode.PhoneExists, errMsg)
		case "邮箱格式不正确":
			response.Error(c, errcode.InvalidEmail, errMsg)
		case "手机号格式不正确":
			response.Error(c, errcode.InvalidPhone, errMsg)
		default:
			response.Error(c, errcode.InternalError, errMsg)
		}
		return
	}

	// 记录审计日志
	adminID, _ := c.Get("userId")
	logger.LogAudit(logger.AuditLog{
		UserID:    adminID.(uint),
		Action:    "UPDATE_USER_INFO",
		Resource:  "user",
		IP:        c.ClientIP(),
		UserAgent: c.GetHeader("User-Agent"),
		Details:   "更新用户ID: " + strconv.FormatUint(id, 10),
	})

	response.Success(c, nil, "更新成功")
}

// UpdateStatus 启用/禁用用户
// @Summary 启用/禁用用户
// @Tags 用户管理
// @Accept json
// @Produce json
// @Param id path int true "用户ID"
// @Param body body model.UpdateUserStatusReq true "状态信息"
// @Success 200 {object} response.Response
// @Router /api/v1/users/:id/status [put]
func (h *UserHandler) UpdateStatus(c *gin.Context) {
	// 获取用户ID参数
	id, err := strconv.ParseUint(c.Param("id"), 10, 32)
	if err != nil {
		response.Error(c, errcode.BadRequest, "用户ID格式错误")
		return
	}

	// 绑定请求参数
	var req model.UpdateUserStatusReq
	if err := c.ShouldBindJSON(&req); err != nil {
		response.Error(c, errcode.BadRequest, "参数错误: "+err.Error())
		return
	}

	// 获取当前管理员ID
	adminID, _ := c.Get("userId")

	// 调用Service层更新
	if err := h.service.UpdateUserStatus(uint(id), &req, adminID.(uint)); err != nil {
		logger.Error("更新用户状态失败", "userId", id, "error", err.Error())

		// 根据错误信息返回不同的错误码
		errMsg := err.Error()
		switch errMsg {
		case "用户不存在":
			response.Error(c, errcode.UserNotFound, errMsg)
		case "不能禁用自己的账号":
			response.Error(c, errcode.PermissionDenied, errMsg)
		default:
			response.Error(c, errcode.InternalError, errMsg)
		}
		return
	}

	// 记录审计日志
	statusText := "启用"
	if req.Status == 0 {
		statusText = "禁用"
	}
	logger.LogAudit(logger.AuditLog{
		UserID:    adminID.(uint),
		Action:    "UPDATE_USER_STATUS",
		Resource:  "user",
		IP:        c.ClientIP(),
		UserAgent: c.GetHeader("User-Agent"),
		Details:   statusText + "用户ID: " + strconv.FormatUint(id, 10),
	})

	response.Success(c, nil, "操作成功")
}

// UpdateRole 修改用户角色
// @Summary 修改用户角色
// @Tags 用户管理
// @Accept json
// @Produce json
// @Param id path int true "用户ID"
// @Param body body model.UpdateUserRoleReq true "角色信息"
// @Success 200 {object} response.Response
// @Router /api/v1/users/:id/role [put]
func (h *UserHandler) UpdateRole(c *gin.Context) {
	// 获取用户ID参数
	id, err := strconv.ParseUint(c.Param("id"), 10, 32)
	if err != nil {
		response.Error(c, errcode.BadRequest, "用户ID格式错误")
		return
	}

	// 绑定请求参数
	var req model.UpdateUserRoleReq
	if err := c.ShouldBindJSON(&req); err != nil {
		response.Error(c, errcode.BadRequest, "参数错误: "+err.Error())
		return
	}

	// 获取当前管理员ID
	adminID, _ := c.Get("userId")

	// 调用Service层更新
	if err := h.service.UpdateUserRole(uint(id), &req, adminID.(uint)); err != nil {
		logger.Error("修改用户角色失败", "userId", id, "error", err.Error())

		// 根据错误信息返回不同的错误码
		errMsg := err.Error()
		switch errMsg {
		case "用户不存在":
			response.Error(c, errcode.UserNotFound, errMsg)
		case "不能修改自己的角色":
			response.Error(c, errcode.PermissionDenied, errMsg)
		case "角色不存在":
			response.Error(c, errcode.BadRequest, errMsg)
		case "角色已被禁用":
			response.Error(c, errcode.BadRequest, errMsg)
		default:
			response.Error(c, errcode.InternalError, errMsg)
		}
		return
	}

	// 记录审计日志
	logger.LogAudit(logger.AuditLog{
		UserID:    adminID.(uint),
		Action:    "UPDATE_USER_ROLE",
		Resource:  "user",
		IP:        c.ClientIP(),
		UserAgent: c.GetHeader("User-Agent"),
		Details:   "修改用户ID: " + strconv.FormatUint(id, 10) + " 的角色为ID: " + strconv.FormatUint(uint64(req.RoleID), 10),
	})

	response.Success(c, nil, "角色修改成功")
}
